package com.ruoyi.chat.LongConnection.handler.nettyService;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.github.dozermapper.core.DozerBeanMapperBuilder;
import com.github.dozermapper.core.Mapper;
import com.ruoyi.chat.LongConnection.model.LongConnectionChatDTO;
import com.ruoyi.chat.LongConnection.model.ReceiveMsgVo;
import com.ruoyi.chat.LongConnection.model.ReturnMsgVo;
import com.ruoyi.chat.LongConnection.model.SendMsgVo;
import com.ruoyi.chat.LongConnection.model.msg.FileMsg;
import com.ruoyi.chat.LongConnection.model.msg.FileMsgVo;
import com.ruoyi.chat.LongConnection.model.msg.TextMsg;
import com.ruoyi.chat.LongConnection.model.msg.TextMsgVo;
import com.ruoyi.chat.LongConnection.util.LongConnectionMsgUtil;
import com.ruoyi.chat.LongConnection.util.LongConnectionUtil;
import com.ruoyi.chat.ab.entity.ChatRecord;
import com.ruoyi.chat.ab.entity.ChatFileData;
import com.ruoyi.chat.ab.service.IChatRecordService;

import com.ruoyi.chat.ab.service.IChatFileDataService;
import com.ruoyi.chat.service.IMinioService;
import com.ruoyi.framework.manager.AsyncManager;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.socket.SocketChannel;
import lombok.SneakyThrows;
import org.checkerframework.checker.units.qual.C;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Component;
import org.springframework.web.client.RestTemplate;

import javax.annotation.PostConstruct;
import java.util.HashMap;
import java.util.TimerTask;
import java.util.concurrent.CountDownLatch;

@Component
public class HasChannelChatService {
    @Autowired
    private IChatRecordService chatrecordService;
    @Autowired
    private IChatFileDataService ChatFileDataService;
    @Autowired
    private IMinioService minioService;


    private static HasChannelChatService mclass;

    @PostConstruct
    public void init() {
        mclass = this;
    }

    private static HashMap<Integer, IChatHandle> map = new HashMap<>();
    private static final ObjectMapper mapper = new ObjectMapper();
    private static final Mapper dozerMapper = DozerBeanMapperBuilder.buildDefault();

    static {
        map.put(LongConnectionChatDTO.TEXT, ((ctx, chatDTO, senderId) -> {
            TextMsg textMsg = mapper.convertValue(chatDTO.getMessage(), new TypeReference<TextMsg>() {
            });
            ChatRecord chatrecord = ChatRecord.ChatRecordReaded(senderId, chatDTO.getReceiverId(), textMsg.getText(), chatDTO.getMsgType());
            mclass.chatrecordService.save(chatrecord);
            TextMsgVo msgVo = dozerMapper.map(chatrecord, TextMsgVo.class);
            SocketChannel channel = LongConnectionUtil.getChannelById(chatDTO.getReceiverId());
            channel.writeAndFlush(LongConnectionMsgUtil.ObjectToWSTextResult(new ReturnMsgVo(ReturnMsgVo.RECEIVE_MSG, new ReceiveMsgVo(chatDTO.getMsgType(), msgVo))));
            ctx.writeAndFlush(LongConnectionMsgUtil.ObjectToWSTextResult(new ReturnMsgVo(ReturnMsgVo.SEND_SUCCESS,
                    new SendMsgVo(chatDTO.getChatId(), msgVo))));

        }));
        map.put(LongConnectionChatDTO.FILE, ((ctx, chatDTO, senderId) -> {
            FileMsg fileMsg = mapper.convertValue(chatDTO.getMessage(), FileMsg.class);
            String url = mclass.minioService.setFile(fileMsg);
            ChatRecord chatrecord = ChatRecord.ChatRecordReaded(senderId, chatDTO.getReceiverId(), url+"_mtx_"+fileMsg.getFileName(), chatDTO.getMsgType());

            mclass.chatrecordService.save(chatrecord);
            ChatFileData ChatFileData = new ChatFileData(chatrecord.getMsgId(), url, fileMsg.getFileName());
            mclass.ChatFileDataService.save(ChatFileData);

            SocketChannel channel = LongConnectionUtil.getChannelById(chatDTO.getReceiverId());
            FileMsgVo fileMsgVo = dozerMapper.map(chatrecord, FileMsgVo.class);
            fileMsgVo.setFileName(fileMsg.getFileName()).setUrl(url);
            channel.writeAndFlush(LongConnectionMsgUtil.ObjectToWSTextResult(new ReturnMsgVo(ReturnMsgVo.RECEIVE_MSG, new ReceiveMsgVo(chatDTO.getMsgType(), fileMsgVo))));
            ctx.writeAndFlush(LongConnectionMsgUtil.ObjectToWSTextResult(new ReturnMsgVo(ReturnMsgVo.SEND_SUCCESS, new SendMsgVo(chatDTO.getChatId(), fileMsgVo))));


        }));
    }

    public static void doChat(Integer msgType, ChannelHandlerContext ctx, LongConnectionChatDTO chatDTO, String senderId) throws Exception {
        map.get(msgType).handle(ctx, chatDTO, senderId);
    }

}
